/*
InteractHandler.cpp
客户端消息处理器
注意：本处仅仅处理消息，改变状态，而不伴随局内对象活动
*/

/*
客户端消息
sync_request
key_input -> uuid, status, key
mouse_input -> uuid, status, value
create_player -> uuid, name, posX, posY
*/

#include <InteractHandler.h>
#include <Level.h>

using namespace std;

/// @brief 传入的简化报头对应的实际含义
unordered_map<string, string> interactDic = {
    { "s", "sync_request" },
    { "k", "key_input" },
    { "m", "mouse_input" },
    { "c", "create_player" },
    { "e", "echo" }
};

InteractHandler::InteractHandler(Level* level) {
    this->level = level;
}

void InteractHandler::handleInteract(const LevelAction& interact,
queue<LevelAction>& responseBuffer) {
    // 根据传入的报头信息决定处理类型
    if (interactDic.find(interact.actionName) == interactDic.end()) { return; }
    string interactCommand = interactDic[interact.actionName];
    if (interactCommand == "sync_request") {
        level->syncGlobalData(responseBuffer);
    }
    if (interactCommand == "key_input") {
        handleKeyInput(interact);
    }
    if (interactCommand == "mouse_input") {
        handleMouseInput(interact);
    }
    if (interactCommand == "create_player") {
        createNewPlayer(interact);
        sendGameLog(interact.paramsList[1] + " joined the game.", responseBuffer);
    }
    if (interactCommand == "echo") {
        level->echo.push(interact.paramsList[0]);
    }
}

void InteractHandler::handleKeyInput(const LevelAction& interact) {
    if (level->players.find(interact.paramsList[0]) != level->players.end()) {
        Player* targetPlayer = &(level->players[interact.paramsList[0]]);
        if (interact.paramsList[2] == "w") {
            targetPlayer->keyWPressed = interact.paramsList[1] == "f";
        }
        else if (interact.paramsList[2] == "a") {
            targetPlayer->keyAPressed = interact.paramsList[1] == "f";
        }
        else if (interact.paramsList[2] == "s") {
            targetPlayer->keySPressed = interact.paramsList[1] == "f";
        }
        else if (interact.paramsList[2] == "d") {
            targetPlayer->keyDPressed = interact.paramsList[1] == "f";
        }
    }
}

void InteractHandler::handleMouseInput(const LevelAction& interact) {
    if (level->players.find(interact.paramsList[0]) != level->players.end()) {
        Player* targetPlayer = &(level->players[interact.paramsList[0]]);
        if (interact.paramsList[1] == "p") {
            targetPlayer->mousePos = Vector2 { stof(interact.paramsList[2]), stof(interact.paramsList[3]) };
        }
        else {
            if (interact.paramsList[2] == "l") {
                targetPlayer->mouseLeftPressed = interact.paramsList[1] == "f";
            }
            else {
                targetPlayer->mouseRightPressed = interact.paramsList[1] == "f";
            }
        }
    }
}

void InteractHandler::createNewPlayer(const LevelAction& interact) {
    level->createNewPlayer(interact);
    printf("Player(%s) has been created on the server.\n", interact.paramsList[0].c_str());
}